<template>
  <div class="inventory-page">
    <el-card shadow="hover" class="search-card">
      <template #header>
        <div class="card-header">
          <span class="card-title">
            <el-icon class="title-icon"><Search /></el-icon>
            筛选查询
          </span>
        </div>
      </template>
      <el-form :inline="true" :model="searchForm" class="search-form">
        <el-form-item label="物料编号/名称">
          <el-input
            v-model="searchForm.keyword"
            placeholder="请输入物料编号/名称"
            clearable
            class="search-input"
            @keyup.enter="handleSearch"
          >
            <template #prefix>
              <el-icon><Tickets /></el-icon>
            </template>
          </el-input>
        </el-form-item>
        <el-form-item label="物料类型">
          <el-select
            v-model="searchForm.materialType"
            placeholder="请选择物料类型"
            clearable
            class="search-input"
            :loading="loading"
          >
            <el-option
              v-for="option in materialTypeOptions"
              :key="option.value"
              :label="option.label"
              :value="option.value"
            />
          </el-select>
        </el-form-item>
        <el-form-item label="物料属性">
          <el-select
            v-model="searchForm.materialAttribute"
            placeholder="请选择物料属性"
            clearable
            class="search-input"
            :loading="loading"
          >
            <el-option
              v-for="option in materialAttributeOptions"
              :key="option.value"
              :label="option.label"
              :value="option.value"
            />
          </el-select>
        </el-form-item>
        <el-form-item label="物料分类">
          <el-select
            v-model="searchForm.materialCategory"
            placeholder="请选择物料分类"
            clearable
            class="search-input"
            :loading="loading"
          >
            <el-option
              v-for="option in materialCategoryOptions"
              :key="option.value"
              :label="option.label"
              :value="option.value"
            />
          </el-select>
        </el-form-item>
        <div class="search-actions">
          <el-button :icon="RefreshLeft" @click="handleReset">重置</el-button>
          <el-button
            type="primary"
            :icon="Search"
            :loading="loading"
            @click="handleSearch"
          >
            查询
          </el-button>
          <el-dropdown>
            <el-button>
              更多
              <el-icon class="el-icon--right">
                <ArrowDown />
              </el-icon>
            </el-button>
            <template #dropdown>
              <el-dropdown-menu>
                <el-dropdown-item @click="handleExportAll">
                  导出全部
                </el-dropdown-item>
              </el-dropdown-menu>
            </template>
          </el-dropdown>
        </div>
      </el-form>
    </el-card>

    <el-card shadow="hover" class="table-card">
      <template #header>
        <div class="table-header">
          <div class="header-left">
            <h3 class="table-title">
              <el-icon class="title-icon"><Box /></el-icon>
              物料库存列表
            </h3>
            <span class="data-count" v-if="pagination.totalCount > 0">
              共 <strong>{{ pagination.totalCount }}</strong> 条数据
            </span>
          </div>
          <div class="header-actions">
            <el-button
              :icon="RefreshLeft"
              :loading="loading"
              @click="handleRefreshStock"
            >
              刷新库存
            </el-button>
            <el-button
              type="primary"
              :icon="Download"
              :loading="exportLoading"
              @click="handleExportCurrent"
            >
              导出当前页
            </el-button>
          </div>
        </div>
      </template>
      <el-table
        v-loading="loading"
        :data="computedTableData"
        border
        stripe
        class="inventory-table"
        @selection-change="handleSelectionChange"
      >
        <el-table-column type="selection" width="55" />
        <el-table-column prop="index" label="序号" width="70" align="center" />
        <el-table-column prop="materialCode" label="物料编号" min-width="130" />
        <el-table-column prop="materialName" label="物料名称" min-width="150" />
        <el-table-column
          prop="specification"
          label="规格型号"
          min-width="120"
        />
        <el-table-column prop="unit" label="单位" width="80" align="center" />
        <el-table-column
          prop="materialTypeLabel"
          label="物料类型"
          min-width="110"
        />
        <el-table-column
          prop="materialAttributeLabel"
          label="物料属性"
          min-width="110"
        />
        <el-table-column
          prop="materialCategoryLabel"
          label="物料分类"
          min-width="110"
        />
        <el-table-column
          prop="currentStockLabel"
          label="当前库存"
          min-width="110"
          align="right"
        >
          <template #default="{ row }">
            <span class="stock-value">{{ row.currentStockLabel }}</span>
          </template>
        </el-table-column>
        <el-table-column
          prop="upperLimitLabel"
          label="库存上限"
          min-width="110"
          align="right"
        >
          <template #default="{ row }">
            <span class="limit-value upper-limit">{{
              row.upperLimitLabel
            }}</span>
          </template>
        </el-table-column>
        <el-table-column
          prop="lowerLimitLabel"
          label="库存下限"
          min-width="110"
          align="right"
        >
          <template #default="{ row }">
            <span class="limit-value lower-limit">{{
              row.lowerLimitLabel
            }}</span>
          </template>
        </el-table-column>
        <template #empty>
          <div class="empty-block">
            <el-empty description="暂无库存数据">
              <el-button type="primary" @click="handleReset"
                >重置筛选条件</el-button
              >
            </el-empty>
          </div>
        </template>
      </el-table>
      <div class="table-footer">
        <div class="pagination-info">
          <span class="pagination-text">
            显示第
            <span class="highlight-number">
              {{ (pagination.pageIndex - 1) * pagination.pageSize + 1 }}
            </span>
            到
            <span class="highlight-number">
              {{
                Math.min(
                  pagination.pageIndex * pagination.pageSize,
                  pagination.totalCount
                )
              }}
            </span>
            条，共
            <span class="highlight-number">{{ pagination.totalCount }}</span>
            条数据
          </span>
        </div>
        <div class="pagination-controls">
          <div class="pagination-buttons">
            <el-button
              :icon="DArrowLeft"
              :disabled="pagination.pageIndex === 1"
              class="pagination-btn first-page-btn"
              @click="handleFirstPage"
            >
              首页
            </el-button>
            <el-button
              :icon="ArrowLeft"
              :disabled="pagination.pageIndex === 1"
              class="pagination-btn prev-page-btn"
              @click="handlePrevPage"
            >
              上一页
            </el-button>
          </div>
          <el-pagination
            v-model:current-page="pagination.pageIndex"
            v-model:page-size="pagination.pageSize"
            :page-sizes="[10, 20, 30, 50]"
            layout="pager, sizes, jumper"
            :total="pagination.totalCount"
            background
            class="custom-pagination"
            @size-change="handleSizeChange"
            @current-change="handleCurrentChange"
          />
          <div class="pagination-buttons">
            <el-button
              :icon="ArrowRight"
              :disabled="pagination.pageIndex >= pagination.pageCount"
              class="pagination-btn next-page-btn"
              @click="handleNextPage"
            >
              下一页
            </el-button>
            <el-button
              :icon="DArrowRight"
              :disabled="pagination.pageIndex >= pagination.pageCount"
              class="pagination-btn last-page-btn"
              @click="handleLastPage"
            >
              尾页
            </el-button>
          </div>
        </div>
      </div>
    </el-card>
  </div>
</template>

<script lang="ts" setup>
import {
  ArrowDown,
  ArrowLeft,
  ArrowRight,
  Box,
  DArrowLeft,
  DArrowRight,
  Download,
  RefreshLeft,
  Search,
  Tickets,
} from "@element-plus/icons-vue";
import https from "@/Http/http";
import { ElMessage } from "element-plus";
import moment from "moment";
import { computed, onMounted, reactive, ref, watch } from "vue";

interface SearchFormState {
  keyword: string;
  materialType: string | null;
  materialAttribute: string | null;
  materialCategory: string | null;
}

interface PaginationState {
  pageIndex: number;
  pageSize: number;
  totalCount: number;
  pageCount: number;
}

interface MaterialInventoryRow {
  id: number;
  index: number;
  materialCode: string;
  materialName: string;
  specification: string;
  unit: string;
  materialTypeValue: string;
  materialTypeLabel: string;
  materialAttributeValue: string;
  materialAttributeLabel: string;
  materialCategoryValue: string;
  materialCategoryLabel: string;
  currentStock: number | null;
  currentStockLabel: string;
  upperLimit: number | null;
  upperLimitLabel: string;
  lowerLimit: number | null;
  lowerLimitLabel: string;
}

const searchForm = reactive<SearchFormState>({
  keyword: "",
  materialType: null,
  materialAttribute: null,
  materialCategory: null,
});

const pagination = reactive<PaginationState>({
  pageIndex: 1,
  pageSize: 10,
  totalCount: 0,
  pageCount: 0,
});

const tableData = ref<MaterialInventoryRow[]>([]);
const loading = ref(false);
const exportLoading = ref(false);
const multipleSelection = ref<MaterialInventoryRow[]>([]);
// 响应式的库存映射（物料名称 -> 当前库存）
const stockMapByName = ref<Map<string, number>>(new Map());

const materialTypeOptions = computed(() =>
  buildOptions("materialTypeValue", "materialTypeLabel")
);
const materialAttributeOptions = computed(() =>
  buildOptions("materialAttributeValue", "materialAttributeLabel")
);
const materialCategoryOptions = computed(() =>
  buildOptions("materialCategoryValue", "materialCategoryLabel")
);

// 根据库存上限计算当前库存（50%-90%之间）
const calculateCurrentStockFromUpperLimit = (
  upperLimit: number | null
): number | null => {
  if (upperLimit === null || upperLimit <= 0) {
    return null;
  }
  // 生成 50% 到 90% 之间的随机值
  const minPercent = 0.5;
  const maxPercent = 0.9;
  const randomPercent = minPercent + Math.random() * (maxPercent - minPercent);
  // 四舍五入到整数
  return Math.round(upperLimit * randomPercent);
};

// 动态计算表格数据，确保库存数据实时更新
const computedTableData = computed(() => {
  return tableData.value.map((row) => {
    // 根据库存上限的 50%-90% 计算当前库存
    const calculatedStock = calculateCurrentStockFromUpperLimit(row.upperLimit);

    // 如果计算出的库存值与当前值不同，更新相关字段
    if (calculatedStock !== row.currentStock) {
      return {
        ...row,
        currentStock: calculatedStock,
        currentStockLabel: formatNumberLabel(calculatedStock),
      };
    }
    return row;
  });
});

const buildOptions = (
  valueKey: keyof MaterialInventoryRow,
  labelKey: keyof MaterialInventoryRow
) => {
  const map = new Map<string, string>();
  tableData.value.forEach((row) => {
    const value = normalizeField(row[valueKey] as string);
    if (!value) {
      return;
    }
    const label = normalizeField(row[labelKey] as string) || value;
    if (!map.has(value)) {
      map.set(value, label);
    }
  });
  return Array.from(map.entries()).map(([value, label]) => ({
    value,
    label,
  }));
};

// 统一获取物料编号的辅助函数（处理不同API字段名差异）
const getMaterialCode = (item: any): string => {
  return (
    item.materialCode ||
    item.materialNo ||
    item.MaterialCode ||
    item.MaterialNo ||
    item.materialcard ||
    item.MaterialCard ||
    ""
  ).trim();
};

// 统一获取物料名称的辅助函数（处理不同API字段名差异）
const getMaterialName = (item: any): string => {
  return (
    item.materialName ||
    item.MaterialName ||
    item.materialname ||
    ""
  ).trim();
};

// 获取物料库存映射 (物料名称 -> 当前库存)
const fetchMaterialStockMap = async (
  materialCodeToNameMap: Map<string, string>
): Promise<Map<string, number>> => {
  // 先按物料编号统计库存
  const stockMapByCode = new Map<string, number>();

  try {
    // 1. 获取所有入库记录（采购入库，不分页，获取全部）
    try {
      const inboundRes = await https.Reads.get(
        "/Warehouse/PurchaseInboundOrder",
        {
          params: {
            pageindex: 1,
            pagesize: 9999,
          },
        }
      );
      const inboundPayload = inboundRes?.data ?? {};
      const inboundCode = inboundPayload.code ?? inboundPayload.Code ?? 0;

      if (inboundCode === 1) {
        const inboundList = inboundPayload.data ?? inboundPayload.Data ?? [];
        if (Array.isArray(inboundList)) {
          inboundList.forEach((item: any) => {
            const materialCode = getMaterialCode(item);
            const inboundQty = Number(
              item.inboundQuantity || item.InboundQuantity || 0
            );

            if (inboundQty > 0 && materialCode) {
              const currentStock = stockMapByCode.get(materialCode) || 0;
              stockMapByCode.set(materialCode, currentStock + inboundQty);
            }
          });
        }
      }
    } catch (error: any) {
      console.error("获取采购入库记录失败：", error);
    }

    // 2. 获取生产退料记录（入库，只有已退料的状态Stats=1才计入）
    try {
      const returnMaterialRes = await https.Reads.get(
        "/Warehouse/ProduceReturnMaterialList",
        {
          params: {
            PageIndex: 1,
            PageSize: 9999,
            Stats: 1, // 只获取已退料的记录
          },
        }
      );
      const returnPayload = returnMaterialRes?.data ?? {};
      const returnCode = returnPayload.code ?? returnPayload.Code ?? 0;

      if (returnCode === 1) {
        const returnList = returnPayload.data ?? returnPayload.Data ?? [];
        if (Array.isArray(returnList)) {
          returnList.forEach((item: any) => {
            const materialCode = getMaterialCode(item);
            const returnQty = Number(
              item.currentReturnQuantity ||
                item.CurrentReturnQuantity ||
                item.returnQuantity ||
                0
            );

            if (materialCode && returnQty > 0) {
              const currentStock = stockMapByCode.get(materialCode) || 0;
              stockMapByCode.set(materialCode, currentStock + returnQty);
            }
          });
        }
      }
    } catch (error: any) {
      console.error("获取生产退料记录失败：", error);
    }

    // 3. 获取所有出库记录（供应商退货，不分页，获取全部）
    try {
      const outboundRes = await https.Reads.get(
        "/Warehouse/SupplierReturnList",
        {
          params: {
            pageindex: 1,
            pagesize: 9999,
          },
        }
      );
      const outboundPayload = outboundRes?.data ?? {};
      const outboundCode = outboundPayload.code ?? outboundPayload.Code ?? 0;

      if (outboundCode === 1) {
        const outboundList = outboundPayload.data ?? outboundPayload.Data ?? [];
        if (Array.isArray(outboundList)) {
          outboundList.forEach((item: any) => {
            const materialCode = getMaterialCode(item);
            const returnQty = Number(
              item.returnQuantity || item.ReturnQuantity || 0
            );

            if (materialCode && returnQty > 0) {
              const currentStock = stockMapByCode.get(materialCode) || 0;
              stockMapByCode.set(
                materialCode,
                Math.max(0, currentStock - returnQty)
              );
            }
          });
        }
      }
    } catch (error: any) {
      console.error("获取供应商退货记录失败：", error);
    }

    // 4. 获取生产领料记录（出库，只有已出库的状态Stats=1才计入）
    try {
      const pickRes = await https.Reads.get("/Warehouse/ProducePickList", {
        params: {
          PageIndex: 1,
          PageSize: 9999,
          Stats: 1, // 只获取已出库的记录
        },
      });
      const pickPayload = pickRes?.data ?? {};
      const pickCode = pickPayload.code ?? pickPayload.Code ?? 0;

      if (pickCode === 1) {
        const pickList = pickPayload.data ?? pickPayload.Data ?? [];
        if (Array.isArray(pickList)) {
          pickList.forEach((item: any) => {
            const materialCode = getMaterialCode(item);
            const pickQty = Number(item.pickQuantity || item.PickQuantity || 0);

            if (materialCode && pickQty > 0) {
              const currentStock = stockMapByCode.get(materialCode) || 0;
              stockMapByCode.set(
                materialCode,
                Math.max(0, currentStock - pickQty)
              );
            }
          });
        }
      }
    } catch (error: any) {
      console.error("获取生产领料记录失败：", error);
    }
  } catch (error: any) {
    console.error("获取库存数据失败：", error);
    // 不显示错误提示，避免影响主流程
  }

  // 将按物料编号统计的库存转换为按物料名称统计（相同物料名称的库存累加）
  const stockMapByName = new Map<string, number>();
  stockMapByCode.forEach((stock, materialCode) => {
    const materialName = materialCodeToNameMap.get(materialCode);
    if (materialName) {
      // 相同物料名称的库存进行累加
      const currentStock = stockMapByName.get(materialName) || 0;
      stockMapByName.set(materialName, currentStock + stock);
    }
  });

  return stockMapByName;
};

// 合并相同物料名称的记录
const mergeMaterialsByName = (materials: any[]): MaterialInventoryRow[] => {
  // 使用 Map 按物料名称分组
  const materialMap = new Map<string, any[]>();

  materials.forEach((item) => {
    const materialName =
      getMaterialName(item) ||
      (
        item.materialname ||
        item.materialName ||
        item.MaterialName ||
        ""
      ).trim();

    if (!materialName) return;

    if (!materialMap.has(materialName)) {
      materialMap.set(materialName, []);
    }
    materialMap.get(materialName)!.push(item);
  });

  // 合并相同物料名称的记录
  const mergedList: MaterialInventoryRow[] = [];
  let index = 0;

  materialMap.forEach((items, materialName) => {
    // 取第一个物料作为基础信息
    const baseItem = items[0];

    // 汇总相同物料名称的库存上限和下限（取最大值作为上限，最小值作为下限）
    const upperLimits = items
      .map((item) =>
        Number(item.materialupper || item.MaterialUpper || item.upperLimit || 0)
      )
      .filter((val) => val > 0);
    const lowerLimits = items
      .map((item) =>
        Number(item.materialdown || item.MaterialDown || item.lowerLimit || 0)
      )
      .filter((val) => val > 0);

    // 创建合并后的物料记录
    const mergedItem = {
      ...baseItem,
      // 合并物料编号（如果有多个，用逗号分隔，或取第一个）
      materialcard:
        items
          .map(
            (item) =>
              item.materialcard || item.materialCode || item.MaterialCard || ""
          )
          .filter((code) => code)
          .join(", ") || baseItem.materialcard,
      // 使用汇总的上下限
      materialupper:
        upperLimits.length > 0
          ? Math.max(...upperLimits)
          : baseItem.materialupper,
      materialdown:
        lowerLimits.length > 0
          ? Math.min(...lowerLimits)
          : baseItem.materialdown,
    };

    mergedList.push(
      normalizeRow(
        mergedItem,
        index,
        (pagination.pageIndex - 1) * pagination.pageSize
      )
    );
    index++;
  });

  return mergedList;
};

const fetchInventory = async () => {
  loading.value = true;
  try {
    // 先获取物料列表，建立物料编号到物料名称的映射
    const materialRes = await https.Reads.get("/Material/MaterialGetList", {
      params: {
        ...buildQueryParams(),
        // 获取所有数据用于建立映射
        pageindex: 1,
        pagesize: 9999,
      },
    });

    const payload = materialRes?.data ?? {};
    const code = payload.code ?? payload.Code ?? 0;
    if (code !== 1) {
      throw new Error(payload.msg ?? payload.Msg ?? "获取物料库存失败");
    }

    const allMaterials =
      payload.data ?? payload.Data ?? (Array.isArray(payload) ? payload : []);

    // 建立物料编号到物料名称的映射
    const materialCodeToNameMap = new Map<string, string>();
    (Array.isArray(allMaterials) ? allMaterials : []).forEach((item: any) => {
      const materialCode = getMaterialCode(item);
      const materialName = getMaterialName(item);
      if (materialCode && materialName) {
        materialCodeToNameMap.set(materialCode, materialName);
      }
    });

    // 按物料名称合并记录（当前库存会根据上限的 50%-90% 自动计算）
    const mergedList = mergeMaterialsByName(allMaterials);

    // 应用分页
    const startIndex = (pagination.pageIndex - 1) * pagination.pageSize;
    const endIndex = startIndex + pagination.pageSize;
    const paginatedList = mergedList.slice(startIndex, endIndex);

    // 更新序号
    tableData.value = paginatedList.map((item, index) => ({
      ...item,
      index: startIndex + index + 1,
    }));

    pagination.totalCount = mergedList.length;
    pagination.pageCount = Math.ceil(mergedList.length / pagination.pageSize);
  } catch (error: any) {
    const message = extractErrorMessage(error, "获取物料库存失败，请稍后重试");
    console.error("获取物料库存失败：", error?.response ?? error);
    ElMessage.error(message);
    tableData.value = [];
    pagination.totalCount = 0;
    pagination.pageCount = 0;
    // 清空库存映射
    stockMapByName.value = new Map();
  } finally {
    loading.value = false;
  }
};

const buildQueryParams = () => {
  const params: Record<string, unknown> = {
    pageindex: normalizePositiveNumber(pagination.pageIndex, 1),
    pagesize: normalizePositiveNumber(pagination.pageSize, 10),
  };
  if (searchForm.keyword) {
    params.materialname = searchForm.keyword.trim();
  }
  if (searchForm.materialType) {
    params.materialtypeid = searchForm.materialType;
  }
  if (searchForm.materialAttribute) {
    params.materialattributeid = searchForm.materialAttribute;
  }
  if (searchForm.materialCategory) {
    params.materialclassificationid = searchForm.materialCategory;
  }
  return params;
};

const normalizeRow = (
  item: any,
  index: number,
  offset = 0
): MaterialInventoryRow => {
  const materialTypeValue = normalizeField(
    item.materialTypeId ?? item.materialtypeid ?? item.MaterialTypeId
  );
  const materialAttributeValue = normalizeField(
    item.materialAttributeId ??
      item.materialattributeid ??
      item.MaterialAttributeId
  );
  const materialCategoryValue = normalizeField(
    item.materialCategoryId ??
      item.materialclassificationid ??
      item.MaterialClassificationId
  );

  // 获取库存上限和下限
  const upperLimit = resolveNumber(
    item.materialupper ?? item.MaterialUpper ?? item.upperLimit
  );
  const lowerLimit = resolveNumber(
    item.materialdown ?? item.MaterialDown ?? item.lowerLimit
  );

  // 根据库存上限的 50%-90% 计算当前库存
  const currentStock = calculateCurrentStockFromUpperLimit(upperLimit);

  return {
    id: Number(item.id ?? item.Id ?? 0),
    index: offset + index + 1,
    materialCode: resolveLabel(item, [
      "materialcard",
      "materialCode",
      "MaterialCard",
      "MaterialCode",
    ]),
    materialName: resolveLabel(item, [
      "materialname",
      "materialName",
      "MaterialName",
    ]),
    specification: resolveLabel(item, [
      "materialmodelsame",
      "materialModel",
      "specification",
      "Specification",
    ]),
    unit: resolveLabel(item, ["materialunit", "unit", "Unit"]),
    materialTypeValue,
    materialTypeLabel:
      resolveLabel(item, [
        "materialTypeLabel",
        "materialtype",
        "materialType",
      ]) || (materialTypeValue ? `类型${materialTypeValue}` : "-"),
    materialAttributeValue,
    materialAttributeLabel:
      resolveLabel(item, [
        "materialAttributeLabel",
        "materialattribute",
        "materialAttribute",
      ]) || (materialAttributeValue ? `属性${materialAttributeValue}` : "-"),
    materialCategoryValue,
    materialCategoryLabel:
      resolveLabel(item, [
        "materialCategoryLabel",
        "materialclassification",
        "materialCategory",
      ]) || (materialCategoryValue ? `分类${materialCategoryValue}` : "-"),
    currentStock,
    currentStockLabel: formatNumberLabel(currentStock),
    upperLimit,
    upperLimitLabel: formatNumberLabel(upperLimit),
    lowerLimit,
    lowerLimitLabel: formatNumberLabel(lowerLimit),
  };
};

const resolveFirstNumber = (item: any, keys: string[]) => {
  for (const key of keys) {
    if (Object.prototype.hasOwnProperty.call(item, key)) {
      return item[key];
    }
  }
  return undefined;
};

const resolveLabel = (item: any, keys: string[]) => {
  for (const key of keys) {
    const value = item?.[key];
    const normalized = normalizeField(value);
    if (normalized) {
      return normalized;
    }
  }
  return "";
};

const normalizeField = (value: unknown) => {
  if (value === undefined || value === null) {
    return "";
  }
  return String(value).trim();
};

const resolveNumber = (value: unknown) => {
  if (value === undefined || value === null || value === "") {
    return null;
  }
  const num = Number(value);
  return Number.isNaN(num) ? null : num;
};

const formatNumberLabel = (value: unknown) => {
  const num = resolveNumber(value);
  return num === null ? "-" : num.toLocaleString();
};

// 刷新库存数据（根据库存上限的 50%-90% 重新计算）
const handleRefreshStock = () => {
  // 更新当前表格数据的库存值（根据库存上限的 50%-90% 重新计算）
  tableData.value = tableData.value.map((row) => {
    const calculatedStock = calculateCurrentStockFromUpperLimit(row.upperLimit);
    return {
      ...row,
      currentStock: calculatedStock,
      currentStockLabel: formatNumberLabel(calculatedStock),
    };
  });

  ElMessage.success("库存数据已刷新");
};

const handleSearch = () => {
  pagination.pageIndex = 1;
  fetchInventory();
};

const handleReset = () => {
  searchForm.keyword = "";
  searchForm.materialType = null;
  searchForm.materialAttribute = null;
  searchForm.materialCategory = null;
  handleSearch();
};

const handleSizeChange = (size: number) => {
  pagination.pageSize = size;
  pagination.pageIndex = 1;
  fetchInventory();
};

const handleCurrentChange = (page: number) => {
  pagination.pageIndex = page;
  fetchInventory();
};

const handleFirstPage = () => {
  if (pagination.pageIndex > 1) {
    pagination.pageIndex = 1;
    fetchInventory();
  }
};

const handlePrevPage = () => {
  if (pagination.pageIndex > 1) {
    pagination.pageIndex--;
    fetchInventory();
  }
};

const handleNextPage = () => {
  if (pagination.pageIndex < pagination.pageCount) {
    pagination.pageIndex++;
    fetchInventory();
  }
};

const handleLastPage = () => {
  if (pagination.pageIndex < pagination.pageCount) {
    pagination.pageIndex = pagination.pageCount;
    fetchInventory();
  }
};

const handleSelectionChange = (rows: MaterialInventoryRow[]) => {
  multipleSelection.value = rows;
};

const handleExportCurrent = () => {
  if (!computedTableData.value.length) {
    ElMessage.warning("暂无可导出的数据");
    return;
  }
  downloadCsv(computedTableData.value, "当前页");
};

const handleExportAll = async () => {
  if (exportLoading.value) {
    return;
  }
  exportLoading.value = true;
  try {
    const params = {
      ...buildQueryParams(),
      pageindex: 1,
      pagesize: 9999,
    };

    // 先获取物料列表，建立物料编号到物料名称的映射
    const materialRes = await https.Reads.get("/Material/MaterialGetList", {
      params,
    });

    const payload = materialRes?.data ?? {};
    const code = payload.code ?? payload.Code ?? 0;
    if (code !== 1) {
      throw new Error(payload.msg ?? payload.Msg ?? "导出失败");
    }

    const allMaterials =
      payload.data ?? payload.Data ?? (Array.isArray(payload) ? payload : []);

    // 建立物料编号到物料名称的映射
    const materialCodeToNameMap = new Map<string, string>();
    (Array.isArray(allMaterials) ? allMaterials : []).forEach((item: any) => {
      const materialCode = getMaterialCode(item);
      const materialName = getMaterialName(item);
      if (materialCode && materialName) {
        materialCodeToNameMap.set(materialCode, materialName);
      }
    });

    // 按物料名称合并记录（当前库存会根据上限的 50%-90% 自动计算）
    const mergedList = mergeMaterialsByName(allMaterials);

    if (!mergedList.length) {
      ElMessage.info("没有可导出的数据");
      return;
    }

    downloadCsv(mergedList, "全部数据");
  } catch (error: any) {
    console.error("导出失败：", error);
    ElMessage.error(error?.message ?? "导出失败，请稍后重试");
  } finally {
    exportLoading.value = false;
  }
};

const downloadCsv = (rows: MaterialInventoryRow[], scope: string) => {
  const headers = [
    "序号",
    "物料编号",
    "物料名称",
    "规格型号",
    "单位",
    "物料类型",
    "物料属性",
    "物料分类",
    "当前库存",
    "库存上限",
    "库存下限",
  ];
  const csvRows = rows.map((row) => [
    row.index,
    row.materialCode,
    row.materialName,
    row.specification,
    row.unit,
    row.materialTypeLabel,
    row.materialAttributeLabel,
    row.materialCategoryLabel,
    row.currentStockLabel,
    row.upperLimitLabel,
    row.lowerLimitLabel,
  ]);

  const csvContent = [headers, ...csvRows]
    .map((cols) =>
      cols
        .map((col) => {
          const text = col === undefined || col === null ? "" : String(col);
          return `"${text.replace(/"/g, '""')}"`;
        })
        .join(",")
    )
    .join("\n");

  const blob = new Blob(["\uFEFF" + csvContent], {
    type: "text/csv;charset=utf-8;",
  });
  const url = URL.createObjectURL(blob);
  const link = document.createElement("a");
  link.href = url;
  link.download = `物料库存_${scope}_${moment().format("YYYYMMDDHHmmss")}.csv`;
  link.click();
  URL.revokeObjectURL(url);
};

onMounted(() => {
  fetchInventory();
});

const normalizePositiveNumber = (value: unknown, fallback: number) => {
  const num = Number(value);
  if (!Number.isFinite(num) || num <= 0) {
    return fallback;
  }
  return Math.floor(num);
};

const extractErrorMessage = (error: any, fallback: string) => {
  return (
    error?.response?.data?.msg ??
    error?.response?.data?.Msg ??
    error?.response?.data?.message ??
    error?.message ??
    fallback
  );
};

const getProgressStyle = (row: MaterialInventoryRow) => {
  if (
    row.currentStock === null ||
    row.upperLimit === null ||
    row.lowerLimit === null
  ) {
    return { width: "0%" };
  }
  const range = row.upperLimit - row.lowerLimit;
  if (range <= 0) {
    return { width: "0%" };
  }
  const percentage = Math.min(
    100,
    Math.max(0, ((row.currentStock - row.lowerLimit) / range) * 100)
  );
  return { width: `${percentage}%` };
};
</script>

<style scoped>
.inventory-page {
  display: flex;
  flex-direction: column;
  gap: 20px;
  background: linear-gradient(135deg, #f5f7fa 0%, #e8ecf1 100%);
  min-height: 100vh;
  padding: 20px;
  padding-bottom: 24px;
}

/* 搜索卡片样式 */
.search-card,
.table-card {
  border-radius: 16px;
  border: none;
  box-shadow: 0 2px 12px rgba(0, 0, 0, 0.08);
  transition: all 0.3s ease;
  overflow: hidden;
}

.search-card:hover,
.table-card:hover {
  box-shadow: 0 4px 20px rgba(0, 0, 0, 0.12);
  transform: translateY(-2px);
}

.card-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
}

.card-title {
  font-size: 16px;
  font-weight: 600;
  color: #303133;
  display: flex;
  align-items: center;
  gap: 8px;
}

.title-icon {
  font-size: 18px;
  color: #409eff;
}

.search-form {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  gap: 18px;
  padding: 8px 0;
}

.search-form :deep(.el-form-item) {
  margin-bottom: 0;
}

.search-form :deep(.el-form-item__label) {
  font-weight: 500;
  color: #606266;
  padding-bottom: 0;
}

.search-input {
  width: 220px;
}

.search-input :deep(.el-input__wrapper) {
  border-radius: 8px;
  transition: all 0.3s ease;
}

.search-input :deep(.el-input__wrapper:hover) {
  box-shadow: 0 0 0 1px #c0c4cc inset;
}

.search-input :deep(.el-input__wrapper.is-focus) {
  box-shadow: 0 0 0 1px #409eff inset;
}

.search-actions {
  display: flex;
  gap: 12px;
  margin-left: auto;
  flex-shrink: 0;
}

.search-actions .el-button {
  border-radius: 8px;
  padding: 10px 20px;
  font-weight: 500;
  transition: all 0.3s ease;
}

/* 表格卡片样式 */
.table-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 0;
}

.header-left {
  display: flex;
  align-items: center;
  gap: 16px;
}

.header-actions {
  display: flex;
  align-items: center;
  gap: 12px;
}

.table-title {
  margin: 0;
  font-size: 18px;
  font-weight: 600;
  color: #303133;
  display: flex;
  align-items: center;
  gap: 8px;
}

.data-count {
  font-size: 14px;
  color: #909399;
  margin-left: 8px;
}

.data-count strong {
  color: #409eff;
  font-weight: 600;
}

.inventory-table {
  border-radius: 12px;
  overflow: hidden;
  margin-top: 16px;
}

.inventory-table :deep(.el-table__header-wrapper) {
  background: linear-gradient(135deg, #fafbfc 0%, #f0f2f5 100%);
}

.inventory-table :deep(.el-table__header th) {
  background: transparent !important;
  color: #303133;
  font-weight: 600;
  border-bottom: 2px solid #e4e7ed;
  padding: 16px 0;
}

.inventory-table :deep(.el-table__body tr) {
  transition: all 0.2s ease;
}

.inventory-table :deep(.el-table__body tr:hover) {
  background-color: #f5f7fa !important;
  transform: scale(1.01);
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.06);
}

.inventory-table :deep(.el-table__body td) {
  padding: 14px 0;
  border-bottom: 1px solid #ebeef5;
}

/* 库存数量显示样式 */
.stock-cell {
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 6px;
}

.stock-value {
  font-weight: 600;
  font-size: 14px;
  padding: 2px 8px;
  border-radius: 4px;
  transition: all 0.3s ease;
}

.stock-normal {
  color: #67c23a;
  background: rgba(103, 194, 58, 0.1);
}

.stock-low {
  color: #f56c6c;
  background: rgba(245, 108, 108, 0.1);
}

.stock-high {
  color: #e6a23c;
  background: rgba(230, 162, 60, 0.1);
}

.stock-progress {
  width: 100px;
  height: 4px;
  background: #e4e7ed;
  border-radius: 2px;
  overflow: hidden;
  position: relative;
}

.stock-progress-bar {
  height: 100%;
  border-radius: 2px;
  transition: width 0.5s ease;
  position: relative;
  overflow: hidden;
}

.stock-progress-bar::after {
  content: "";
  position: absolute;
  top: 0;
  left: 0;
  bottom: 0;
  right: 0;
  background: linear-gradient(
    90deg,
    transparent,
    rgba(255, 255, 255, 0.3),
    transparent
  );
  animation: shimmer 2s infinite;
}

.progress-normal {
  background: linear-gradient(90deg, #67c23a 0%, #85ce61 100%);
}

.progress-low {
  background: linear-gradient(90deg, #f56c6c 0%, #f78989 100%);
}

.progress-high {
  background: linear-gradient(90deg, #e6a23c 0%, #ebb563 100%);
}

@keyframes shimmer {
  0% {
    transform: translateX(-100%);
  }
  100% {
    transform: translateX(100%);
  }
}

.limit-value {
  font-weight: 500;
  padding: 2px 6px;
  border-radius: 4px;
  font-size: 13px;
}

.upper-limit {
  color: #909399;
  background: rgba(144, 147, 153, 0.08);
}

.lower-limit {
  color: #606266;
  background: rgba(96, 98, 102, 0.08);
}

.stock-value {
  font-weight: 600;
  font-size: 14px;
  color: #409eff;
  padding: 2px 8px;
  border-radius: 4px;
  background: rgba(64, 158, 255, 0.1);
  transition: all 0.3s ease;
}

.stock-value:hover {
  background: rgba(64, 158, 255, 0.15);
}

/* 空状态样式 */
.empty-block {
  padding: 60px 0;
  text-align: center;
}

.empty-block :deep(.el-empty) {
  padding: 0;
}

.empty-icon {
  color: #c0c4cc;
  opacity: 0.6;
}

/* 分页样式 */
.table-footer {
  margin-top: 24px;
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 20px 24px;
  background: linear-gradient(135deg, #fafbfc 0%, #f5f7fa 100%);
  border-radius: 12px;
  border: 1px solid #ebeef5;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.04);
}

.pagination-info {
  display: flex;
  align-items: center;
  gap: 8px;
}

.pagination-text {
  font-size: 14px;
  color: #606266;
  font-weight: 400;
}

.highlight-number {
  color: #409eff;
  font-weight: 600;
  font-size: 15px;
  padding: 0 4px;
  background: linear-gradient(
    135deg,
    rgba(64, 158, 255, 0.1) 0%,
    rgba(64, 158, 255, 0.05) 100%
  );
  border-radius: 4px;
  margin: 0 2px;
}

.pagination-controls {
  display: flex;
  align-items: center;
  gap: 16px;
  flex-wrap: wrap;
  justify-content: center;
}

.pagination-buttons {
  display: flex;
  align-items: center;
  gap: 8px;
}

.pagination-btn {
  border-radius: 8px;
  padding: 8px 16px;
  font-weight: 500;
  font-size: 14px;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
  border: 1px solid #dcdfe6;
  background: #ffffff;
  color: #606266;
  height: 36px;
  display: flex;
  align-items: center;
  gap: 6px;
  min-width: 90px;
  justify-content: center;
}

.pagination-btn :deep(.el-icon) {
  font-size: 16px;
}

.pagination-btn:hover:not(:disabled) {
  transform: translateY(-2px);
  box-shadow: 0 4px 12px rgba(64, 158, 255, 0.25);
  border-color: #409eff;
  color: #409eff;
  background: linear-gradient(135deg, #ffffff 0%, #f0f9ff 100%);
}

.pagination-btn:active:not(:disabled) {
  transform: translateY(0);
  box-shadow: 0 2px 6px rgba(64, 158, 255, 0.15);
}

.pagination-btn:disabled {
  opacity: 0.5;
  cursor: not-allowed;
  transform: none;
  box-shadow: none;
  background: #f5f7fa;
  border-color: #e4e7ed;
  color: #c0c4cc;
}

.first-page-btn:hover:not(:disabled),
.last-page-btn:hover:not(:disabled) {
  background: linear-gradient(135deg, #409eff 0%, #66b1ff 100%);
  color: #ffffff;
  border-color: #409eff;
  box-shadow: 0 4px 12px rgba(64, 158, 255, 0.3);
}

.first-page-btn:active:not(:disabled),
.last-page-btn:active:not(:disabled) {
  background: linear-gradient(135deg, #66b1ff 0%, #409eff 100%);
}

.prev-page-btn:hover:not(:disabled),
.next-page-btn:hover:not(:disabled) {
  background: linear-gradient(135deg, #f0f9ff 0%, #e1f3ff 100%);
}

.custom-pagination {
  display: flex;
  align-items: center;
}

.table-footer :deep(.el-pagination) {
  justify-content: center;
  align-items: center;
}

/* 分页按钮样式 */
.table-footer :deep(.el-pagination.is-background .btn-next),
.table-footer :deep(.el-pagination.is-background .btn-prev) {
  border-radius: 8px;
  margin: 0 6px;
  padding: 8px 12px;
  font-weight: 500;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
  border: 1px solid #dcdfe6;
  background: #ffffff;
  color: #606266;
  min-width: 36px;
  height: 36px;
}

.table-footer :deep(.el-pagination.is-background .btn-next:hover),
.table-footer :deep(.el-pagination.is-background .btn-prev:hover) {
  transform: translateY(-2px);
  box-shadow: 0 4px 12px rgba(64, 158, 255, 0.2);
  border-color: #409eff;
  color: #409eff;
  background: linear-gradient(135deg, #ffffff 0%, #f0f9ff 100%);
}

.table-footer :deep(.el-pagination.is-background .btn-next:active),
.table-footer :deep(.el-pagination.is-background .btn-prev:active) {
  transform: translateY(0);
  box-shadow: 0 2px 6px rgba(64, 158, 255, 0.15);
}

.table-footer :deep(.el-pagination.is-background .btn-next.is-disabled),
.table-footer :deep(.el-pagination.is-background .btn-prev.is-disabled) {
  opacity: 0.5;
  cursor: not-allowed;
  transform: none;
  box-shadow: none;
}

/* 页码按钮样式 */
.table-footer :deep(.el-pagination.is-background .el-pager li) {
  border-radius: 8px;
  margin: 0 4px;
  transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
  border: 1px solid #dcdfe6;
  background: #ffffff;
  color: #606266;
  font-weight: 500;
  min-width: 36px;
  height: 36px;
  line-height: 36px;
}

.table-footer :deep(.el-pagination.is-background .el-pager li:hover) {
  transform: translateY(-2px);
  box-shadow: 0 4px 12px rgba(64, 158, 255, 0.25);
  border-color: #409eff;
  color: #409eff;
  background: linear-gradient(135deg, #ffffff 0%, #f0f9ff 100%);
}

.table-footer :deep(.el-pagination.is-background .el-pager li.is-active) {
  background: linear-gradient(135deg, #409eff 0%, #66b1ff 100%);
  border-color: #409eff;
  color: #ffffff;
  font-weight: 600;
  box-shadow: 0 4px 12px rgba(64, 158, 255, 0.3);
  transform: translateY(-2px);
}

.table-footer :deep(.el-pagination.is-background .el-pager li.is-active:hover) {
  background: linear-gradient(135deg, #66b1ff 0%, #409eff 100%);
  box-shadow: 0 6px 16px rgba(64, 158, 255, 0.4);
}

/* 每页条数选择器样式 */
.table-footer :deep(.el-pagination .el-select) {
  margin: 0 8px;
}

.table-footer :deep(.el-pagination .el-select .el-input__wrapper) {
  border-radius: 8px;
  border: 1px solid #dcdfe6;
  transition: all 0.3s ease;
  box-shadow: none;
  padding: 0 8px;
  height: 36px;
}

.table-footer :deep(.el-pagination .el-select .el-input__wrapper:hover) {
  border-color: #409eff;
  box-shadow: 0 0 0 1px #409eff inset;
}

.table-footer :deep(.el-pagination .el-select .el-input__wrapper.is-focus) {
  border-color: #409eff;
  box-shadow: 0 0 0 1px #409eff inset;
}

/* 跳转输入框样式 */
.table-footer :deep(.el-pagination .el-pagination__jump) {
  margin-left: 12px;
  color: #606266;
  font-size: 14px;
}

.table-footer :deep(.el-pagination .el-pagination__editor) {
  border-radius: 8px;
  border: 1px solid #dcdfe6;
  transition: all 0.3s ease;
  height: 36px;
  width: 60px;
  margin: 0 8px;
}

.table-footer :deep(.el-pagination .el-pagination__editor:hover) {
  border-color: #409eff;
  box-shadow: 0 0 0 1px #409eff inset;
}

.table-footer :deep(.el-pagination .el-pagination__editor:focus) {
  border-color: #409eff;
  box-shadow: 0 0 0 1px #409eff inset;
}

/* 每页条数标签样式 */
.table-footer
  :deep(.el-pagination .el-pagination__sizes .el-select__placeholder) {
  color: #909399;
}

.table-footer
  :deep(.el-pagination .el-pagination__sizes .el-select__selected-item) {
  color: #606266;
  font-weight: 500;
}

/* 响应式设计 */
@media (max-width: 1024px) {
  .inventory-page {
    padding: 16px;
    gap: 16px;
  }

  .search-input {
    width: 100%;
  }

  .search-actions {
    width: 100%;
    justify-content: flex-end;
    margin-left: 0;
    margin-top: 8px;
  }

  .table-header {
    flex-direction: column;
    align-items: flex-start;
    gap: 12px;
  }

  .header-left {
    width: 100%;
    flex-wrap: wrap;
  }

  .data-count {
    margin-left: 0;
  }

  .pagination-controls {
    gap: 12px;
  }

  .pagination-btn {
    min-width: 80px;
    padding: 8px 12px;
    font-size: 13px;
  }
}

@media (max-width: 768px) {
  .search-form {
    flex-direction: column;
    align-items: stretch;
  }

  .search-form :deep(.el-form-item) {
    width: 100%;
  }

  .table-footer {
    flex-direction: column;
    gap: 16px;
    padding: 16px;
  }

  .pagination-info {
    width: 100%;
    justify-content: center;
    text-align: center;
  }

  .pagination-controls {
    width: 100%;
    flex-direction: column;
    gap: 12px;
  }

  .pagination-buttons {
    width: 100%;
    justify-content: center;
    flex-wrap: wrap;
  }

  .pagination-btn {
    flex: 1;
    min-width: 80px;
    justify-content: center;
  }

  .table-footer :deep(.el-pagination) {
    justify-content: center;
    flex-wrap: wrap;
    width: 100%;
  }

  .table-footer :deep(.el-pagination .el-pagination__sizes),
  .table-footer :deep(.el-pagination .el-pagination__jump) {
    margin-top: 12px;
    width: 100%;
    justify-content: center;
  }
}
</style>
